package com.supsi.segreteria.client;

import java.util.*;


/**
 * Created with IntelliJ IDEA.
 * User: cristian
 * Date: 5/18/12
 * Time: 4:28 PM
 * To change this template use File | Settings | File Templates.
 */
public class GUIModel implements IClientObserver {

    private List fObservers = new ArrayList();
    private List fContatti = new ArrayList<String>();
    private String fNumero, fMessaggio;
    private Configurator conf = Configurator.getInstance();
    private ClientCommunicationManager comm = ClientCommunicationManager.getInstance();
    private Message[] allMessages;
    private Message[] newMessages;
    private String chatHistory = "";


    /**
     * class constructor
     */
    public GUIModel(){
        //le's register to the communication manager for receiving new messages notifications
        comm.addObserver(this);
    }

    /**
     * add interested observers
     *
     * @param observer
     */
    public void addObserver(IGUIObserver observer){
        fObservers.add(observer);
    }

    /**
     * registered observer notification function
     */
    public void notifyObservers(){

        Iterator iterator = fObservers.iterator();

        while (iterator.hasNext()){
            IGUIObserver obElement = (IGUIObserver)iterator.next();

            //call object's update function
            obElement.update(this);
        }

    }

    // call notifyObservers every time data in the Model has changed

    /**
     * add and save new contact
     * @param lNewNumber    Long Contact Number
     * @param sNewName      String Contact name
     */
    public void addNewContact(Long lNewNumber, String sNewName) {
        conf.addressBook.addEntry(lNewNumber, sNewName);
        conf.saveAddressBook();
    }

    /**
     * remove contact and save addressbook
     * @param lUserNumber    Long user number
     * @param sUserName      String user name
     */
    public void removeContact(Long lUserNumber, String sUserName) {
        conf.addressBook.removeEntry(lUserNumber, sUserName);
        conf.saveAddressBook();
    }

    /**
     * return address book entry array
     * @return AddressBookEntry[] array of address book entries
     */
    public Configurator.AddressBook.AddressBookEntry[] getAddressBook() {
        return conf.addressBook.getAddresses();
    }

    /**
     * snd message to user via server
     * @param userNumber    Long user number
     * @param message       String message
     */
    public void sendMessage(Long userNumber, String message) {

        String serverAnswer = comm.messageTo(userNumber.toString(),message);
        chatHistory+= "server answered: "+serverAnswer+"\n";

        notifyObservers();
    }

    /**
     * download all messages from server
     */
    public void retrieveMessages(){

        allMessages = comm.getMessages(MessagesToRetreive.ALL);

        if (allMessages.length > 0) {
            chatHistory += "\nhere are all your messages:\n";

            for (int i = 0; i < allMessages.length; i++) {

                String formattedMessage = "n:"+(i+1)+" from: " + conf.addressBook.getUserName(allMessages[i].getSender())  + " on date: " + allMessages[i].getDate() + " message: " + allMessages[i].getMessage() + "\n";
                chatHistory += formattedMessage;
            }
        } else {
            chatHistory+= "there are no messages for you.\n";
        }

        //notify about updated chat history
        notifyObservers();

    }

    public void retrieveNewMessages(){
        newMessages = comm.getMessages(MessagesToRetreive.NEW);

        if (newMessages.length > 0) {
            chatHistory += "\nhere are your new messages:\n";

            for (int i = 0; i < newMessages.length; i++) {

                String formattedMessage = "n:"+(i+1)+" from: " + newMessages[i].getSender() + " on date: " + newMessages[i].getDate() + " message: " + newMessages[i].getMessage() + "\n";
                chatHistory += formattedMessage;
            }
        } else {
            chatHistory+= "there are no new messages for you.\n";
        }

        //notify about updated chat history
        notifyObservers();
    }

    public void deleteAllMessages(){
        String answer = comm.deleteMessage(0);

        chatHistory +="deleting all messages:" +answer+"\n";

        notifyObservers();
    }

    public void deleteMessage(int msgNumber){
        String answer = comm.deleteMessage(msgNumber);

        chatHistory +="deleting message "+msgNumber+":" +answer+"\n";

        notifyObservers();
    }

    /**
     * clear chat history
     */
    public void clearChatHistory(){
        chatHistory = "";
        notifyObservers();
    }

    /**
     * load all messages into GUI
     * @return Message[] array of messages
     */
    public String loadChatHistory(){
        return chatHistory;
    }


    /**
     * open connection and present itself to server
     * @param nickname String
     */
    public void connectToServer(String nickname){
        if (comm.connectToServer(conf.getServerAddress())){
            String answer = comm.welcomeMessage(nickname);
            chatHistory+="connecting to server: "+answer+"\n"; }
        else {
            chatHistory+="server not ready\n";
        }

        notifyObservers();
    }

    public void disconnectFromServer(){
        comm.disconnectFromServer();
    }

    @Override
    public void update(IClientSubject o) {
        //we're being invoked by ClientCommunicationManager for new message notification
        //so we call the retrieveNewMessages function.
        if (o.getState().equals("NOTIFY")) {
            chatHistory+= "\n -->there are new messages for you!\n";
            notifyObservers();
        }
    }

}
